package com.hmall.trade.controller;

import com.hmall.common.exception.BizIllegalException;
import com.hmall.common.utils.BeanUtils;
import com.hmall.common.utils.UserContext;
import com.hmall.trade.domain.dto.OrderFormDTO;
import com.hmall.trade.domain.vo.OrderVO;
import com.hmall.trade.service.IOrderService;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiImplicitParam;
import io.swagger.annotations.ApiOperation;
import lombok.RequiredArgsConstructor;
import org.apache.ibatis.annotations.Param;
import org.redisson.api.RLock;
import org.redisson.api.RedissonClient;
import org.springframework.web.bind.annotation.*;

import java.util.concurrent.TimeUnit;

/**
 * @author zzw
 */
@Api(tags = "订单管理接口")
@RestController
@RequestMapping("/orders")
@RequiredArgsConstructor
public class OrderController {
    private final IOrderService orderService;

    private final RedissonClient redissonClient;

    @ApiOperation("根据id查询订单")
    @GetMapping("{id}")
    public OrderVO queryOrderById(@Param("订单id") @PathVariable("id") Long orderId) {
        return BeanUtils.copyBean(orderService.getById(orderId), OrderVO.class);
    }

    @ApiOperation("创建订单")
    @PostMapping
    public Long createOrder(@RequestBody OrderFormDTO orderFormDTO) {
        // 方案1：使用分布式锁，防止订单重复提交
        Long userId = UserContext.getUser();
        String lockKey = "hmall:order:lock:" + userId;
        RLock lock = redissonClient.getLock(lockKey);
        try {
            // 开启看门狗，自动续期，防止死锁
            boolean success = lock.tryLock(3, -1, TimeUnit.SECONDS);
            if (!success) {
                throw new BizIllegalException("订单重复提交");
            }
            return orderService.createOrder(orderFormDTO);
        }
        catch (InterruptedException e) {
            throw new RuntimeException(e);
        }
        finally {
            lock.unlock();
        }

        //        // 方案2：使用token+redis，防止订单重复提交
        //        // 1.生成token
        //        Map<String, Object> claims = new HashMap<>();
        //        claims.put("userId", UserContext.getUser());
        //        String token = JWTUtil.createToken(claims, "hmall".getBytes());
        //        // 2.保存token
        //        redissonClient.getBucket("hmall:order:token:" + token).set(orderFormDTO);
        //        // 3.返回 token 给前端
        //
        //        // 1.获取token
        //        String tokenFromClient = String.valueOf(redissonClient.getBucket("hmall:order:token:" + token));
        //        if (tokenFromClient == null) {
        //            throw new RuntimeException("订单重复提交");
        //        }
        //        // 2.删除 token
        //        redissonClient.getBucket("hmall:order:token:" + token).delete();
        //        // 3.创建订单
        //        return orderService.createOrder(orderFormDTO);

    }

    @ApiOperation("标记订单已支付")
    @ApiImplicitParam(name = "orderId", value = "订单id", paramType = "path")
    @PutMapping("/{orderId}")
    public void markOrderPaySuccess(@PathVariable("orderId") Long orderId) {
        orderService.markOrderPaySuccess(orderId);
    }
}
